package com.boot.security.server.service.impl.mffl.Timer;

import com.boot.security.server.dao.mffl.MfflUserDao;
import com.boot.security.server.model.mffl.*;
import com.boot.security.server.service.impl.mffl.MfflConsultation.MfflConsultationService;
import com.boot.security.server.service.impl.mffl.MfflContract.MfflContractService;
import com.boot.security.server.service.impl.mffl.MfflLawyerletter.MfflLawyerletterService;
import com.boot.security.server.service.impl.mffl.MfflOrder.MfflOrderService;
import com.boot.security.server.service.impl.mffl.MfflService.MfflServiceImpl;
import com.boot.security.server.utils.mffl.MfflRedisUtil;
import com.boot.security.server.utils.mffl.MfflServiceNameMping;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.PropertySource;
import org.springframework.scheduling.annotation.EnableScheduling;
import org.springframework.scheduling.annotation.Scheduled;
import org.springframework.stereotype.Component;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.StringUtils;
import java.util.ArrayList;
import java.util.List;

/**
 * 定时任务处理器
 */

@Component
@EnableScheduling
@PropertySource("classpath:application.yml")
/*下面注解待删除*/
//@RestController
//@RequestMapping(value = "MfflConsultationTimerTask")
public class MfflConsultationTimerTask {
    //律师函业务
    @Autowired
    private MfflLawyerletterService MfflLawyerletterService;
    //合同业务
    @Autowired
    private MfflContractService MfflContractService;
    //咨询业务
    @Autowired
    private MfflConsultationService MfflConsultationService;
    //redis缓存
    @Autowired
    private MfflRedisUtil MfflRedisUtil;
    //服务表
    @Autowired
    private MfflServiceImpl MfflServiceImpl;
    //定时任务
    @Autowired
    private TimerTask timertask;


    /**
     * 专业咨询定时任务
     * 项目启动后执行
     * 每*分钟执行一次
     * <p>
     * 1.处理用户发布专业咨询，没有答案而过期的数据（退款）
     * 2.处理用户发布的专业咨询，有回复而没有设为最佳答案的数据（默认最早回复的为最佳答案）
     */
    @Transactional(rollbackFor = Exception.class)
    @Scheduled(cron = "${Timer.ExecutionTime}")
    //@GetMapping(value = "ProfessionalConsultationTimer")
    public void ProfessionalConsultationTimer() throws Exception {
        System.out.println("【专业咨询定时任务】执行中。。。");
        //有回复未设最佳答案时间（毫秒）
        String ConfirmTime = getRedis(MfflServiceNameMping.serviceNames.name(), MfflServiceNameMping.ProfessionalConsultation.name() + "_ConfirmTime", 2L);
        //没有回复退款时间（毫秒）
        String RefuseTime = getRedis(MfflServiceNameMping.serviceNames.name(), MfflServiceNameMping.ProfessionalConsultation.name() + "_RefuseTime", 2L);

        //获取待处理业务
        List<MfflConsultation> timerTaskData = MfflConsultationService.getTimerTaskData(Long.parseLong(ConfirmTime), Long.parseLong(RefuseTime));
        List<MfflConsultation> ConfirmList = new ArrayList<>(); //到时以后答案未设最佳答案数据
        List<MfflConsultation> RefuseList = new ArrayList<>();  //未有答案给于退款数据
        //分类
        for (MfflConsultation item : timerTaskData) {
            if (item.getReplyNumber() == 0) {
                RefuseList.add(item);
            } else {
                ConfirmList.add(item);
            }
        }
        try {
            /**
             * 1.到期有回复未设为最佳答案的
             */
            if (ConfirmList.size() != 0) {
                for (MfflConsultation item : ConfirmList) {
                    try {
                        timertask.ProfessionalConsultationTimer_ConfirmList(item);
                    } catch (Exception e) {
                        continue;
                    }
                }
            }

            /**
             * 2.未有答案给于退款数据
             */
            if (RefuseList.size() != 0) {
                for (MfflConsultation item : RefuseList) {
                    try {
                        timertask.ProfessionalConsultationTimer_RefuseList(item);
                    } catch (Exception e) {
                        continue;
                    }
                }
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        System.out.println("【专业咨询定时任务】执行完成");
    }


    /**
     * 律师函定时任务
     * 项目启动后执行
     * 每*分钟执行一次
     * <p>
     * 1.用户下单后,律师多久没有接单后自动视为拒绝接受服务。
     * 2.律师发送律件后，用户多有没有确认视为已完成。
     */
    @Scheduled(cron = "${Timer.ExecutionTime}")
    //@GetMapping(value = "lawyerletterTimer")
    public void lawyerletterTimer() {
        System.out.println("【律师函定时任务】执行中。。。");
        //用户未点击完成超时时间。
        String ConfirmTime = getRedis(MfflServiceNameMping.serviceNames.name(), MfflServiceNameMping.LawyerLetter.name() + "_ConfirmTime", 3L);
        //律师超时未接受时间。
        String RefuseTime = getRedis(MfflServiceNameMping.serviceNames.name(), MfflServiceNameMping.LawyerLetter.name() + "_RefuseTime", 3L);

        //获取待处理业务
        List<MfflLawyerletter> timerTaskData = MfflLawyerletterService.getTimerTaskData(Long.parseLong(ConfirmTime), Long.parseLong(RefuseTime));
        List<MfflLawyerletter> ConfirmList = new ArrayList<>(); //律师已发送邮件，用户超时未点击完成服务
        List<MfflLawyerletter> RefuseList = new ArrayList<>();  //用户发布律师函，律师超时未接单
        //分类
        for (MfflLawyerletter item : timerTaskData) {
            if (item.getState() == 0) {
                RefuseList.add(item);
            } else {
                ConfirmList.add(item);
            }
        }
        /**
         * 1.律师已发货，用户超时未点击完成服务。视为已完成
         */
        if (ConfirmList.size() != 0) {
            for (MfflLawyerletter item : ConfirmList) {
                try {
                    timertask.lawyerletterTimer_ConfirmList(item);
                } catch (Exception e) {
                    continue;
                }

            }
        }

        /**
         * 2.用户已下单律师函，律师超时未接单。视为拒绝
         */
        if (RefuseList.size() != 0) {
            for (MfflLawyerletter item : RefuseList) {
                try {
                    timertask.lawyerletterTimer_RefuseList(item);
                } catch (Exception e) {
                    continue;
                }
            }
        }

        System.out.println("【律师函定时任务】执行完成");
    }


    /**
     * 合同定时任务
     * 项目启动后执行
     * 每*分钟执行一次
     * <p>
     * 1.用户下单后,律师多久没有接单后自动视为拒绝接受服务。
     * 2.律师发送律件后，用户多有没有确认视为已完成。
     */
    @Transactional(rollbackFor = Exception.class)
    @Scheduled(cron = "${Timer.ExecutionTime}")
    //@GetMapping(value = "ContractTimer")
    public void ContractTimer() throws Exception {
        System.out.println("【合同定时任务】执行中。。。");
        /**
         * 查询缓存是否有服务信息，没有查询数据库
         */
        //用户未点击完成超时时间[合同审核]。
        String ContractAudit_ConfirmTime = getRedis(MfflServiceNameMping.serviceNames.name(), MfflServiceNameMping.ContractAudit.name() + "_ConfirmTime", 4L);
        //律师超时未接受时间[合同审核]。
        String ContractAudit_RefuseTime = getRedis(MfflServiceNameMping.serviceNames.name(), MfflServiceNameMping.ContractAudit.name() + "_RefuseTime", 4L);
        //用户未点击完成超时时间[合同定制]。
        String ContractCustomization_ConfirmTime = getRedis(MfflServiceNameMping.serviceNames.name(), MfflServiceNameMping.ContractCustomization.name() + "_ConfirmTime", 5L);
        //律师超时未接受时间[合同定制]。
        String ContractCustomization_RefuseTime = getRedis(MfflServiceNameMping.serviceNames.name(), MfflServiceNameMping.ContractCustomization.name() + "_RefuseTime", 5L);

        //获取待处理业务
        List<MfflContract> ContractAuditTimer_timerTaskData = MfflContractService.getContractAuditTimerTaskData(Long.parseLong(ContractAudit_ConfirmTime), Long.parseLong(ContractAudit_RefuseTime), Long.parseLong(ContractCustomization_ConfirmTime), Long.parseLong(ContractCustomization_RefuseTime));
        List<MfflContract> ConfirmList = new ArrayList<>(); //律师已发送邮件，用户超时未点击完成服务
        List<MfflContract> RefuseList = new ArrayList<>();  //用户发布合同，律师超时未接单
        //分类
        for (MfflContract item : ContractAuditTimer_timerTaskData) {
            if (item.getState() == 0) {
                RefuseList.add(item);
            } else {
                ConfirmList.add(item);
            }
        }

        /**
         * 1.律师已确认完成，用户超时未点击完成服务。视为已完成
         */
        if (ConfirmList.size() != 0) {
            for (MfflContract item : ConfirmList) {
                try {
                    timertask.ContractTimer_ConfirmList(item);
                } catch (Exception e) {
                    continue;
                }
            }
        }

        /**
         * 2.用户已下单合同，律师超时未接单。视为拒绝
         */
        if (RefuseList.size() != 0) {
            for (MfflContract item : RefuseList) {
                try {
                    timertask.ContractTimer_RefuseList(item);
                } catch (Exception e) {
                    continue;
                }
            }
        }
        System.out.println("【合同定时任务】执行完成");
    }

    /**
     * 获取服务设置的过期时间
     * 缓存到redis中
     *
     * @param prefix 前缀
     * @param name   名字（"_ConfirmTime" OR "_RefuseTime"）
     * @param id     服务id
     * @return
     */
    public String getRedis(String prefix, String name, Long id) {
        String SetUpTime = MfflRedisUtil.getRedis(prefix, name);
        if (StringUtils.isEmpty(SetUpTime)) {
            MfflService byServiceId = MfflServiceImpl.getByServiceId(id);
            if (byServiceId != null &&
                    !StringUtils.isEmpty(byServiceId.getConfirmTime()) && !StringUtils.isEmpty(byServiceId.getRefuseTime()) &&
                    "0".equals(byServiceId.getConfirmTime()) && "0".equals(byServiceId.getRefuseTime())) {

                String[] string = name.split("_");
                if ("ConfirmTime".equals(string[1])) {
                    MfflRedisUtil.saveRedis(prefix, name, byServiceId.getConfirmTime());
                    MfflRedisUtil.saveRedis(prefix, string[0] + "_RefuseTime", byServiceId.getRefuseTime());
                    SetUpTime = byServiceId.getConfirmTime();
                } else {
                    MfflRedisUtil.saveRedis(prefix, name, byServiceId.getConfirmTime());
                    MfflRedisUtil.saveRedis(prefix, string[0] + "_ConfirmTime", byServiceId.getRefuseTime());
                    SetUpTime = byServiceId.getRefuseTime();
                }
            } else {
                String Millisecond = "259200000";
                String[] string = name.split("_");
                if ("ConfirmTime".equals(string[1])) {
                    MfflRedisUtil.saveRedis(prefix, name, Millisecond);
                    MfflRedisUtil.saveRedis(prefix, string[0] + "_RefuseTime", Millisecond);
                    SetUpTime = byServiceId.getConfirmTime();
                } else {
                    MfflRedisUtil.saveRedis(prefix, name, Millisecond);
                    MfflRedisUtil.saveRedis(prefix, string[0] + "_ConfirmTime", Millisecond);
                    SetUpTime = "259200000";
                }
            }
        }
        return SetUpTime;
    }
}